//
//  Canvas.cpp
//  Olivia
//
//  Created by 钟昆达 on 13-3-20.
//
//

#include "Canvas.h"
#include "OgreSceneManager.h"
#include "OgreRoot.h"
#include "OgreManualObject.h"
#include "../../lua_ogre/camerabinding.h"
#include "OgreFramework.h"
#include "b2World.h"
#include "PhysicsDrawer.h"
#include "b2Body.h"
#include "b2CircleShape.h"

namespace Olivia {
    
    Canvas *g_active_canvas = 0;
    
Canvas::Canvas() : m_view_port(NULL), m_name("untitled_canvas"), m_show_physics(true), m_physics_drawer(NULL)
{
    m_scn = Ogre::Root::getSingleton().createSceneManager(Ogre::ST_GENERIC, "Canvas");
    m_cam = m_scn->createCamera("MainCamera");
    
    Ogre::RenderWindow *wnd = OgreFramework::getSingleton().m_pRenderWnd;
    wnd->addViewport(m_cam);
    float width(wnd->getWidth()), height(wnd->getHeight());
    m_cam->setProjectionType(Ogre::PT_ORTHOGRAPHIC);
    m_cam->setOrthoWindow(width, height);
    m_cam->setPosition(.5f * width, .5f * height, 1000.0f);
    m_cam->setDirection(.0f, .0f, -1.0f);
    m_cam->setNearClipDistance(1.0f);
    
    m_drawer = m_scn->createManualObject("Drawer");
    m_drawer->setDynamic(true);
    m_drawer->begin("BaseWhiteNoLighting", Ogre::RenderOperation::OT_TRIANGLE_LIST, Ogre::ResourceGroupManager::INTERNAL_RESOURCE_GROUP_NAME);
//    Ogre::ColourValue red(.5f, .0f, .0f);
//    m_drawer->position(Ogre::Vector3(.5f * width, .5f * height, .0f));
//    m_drawer->colour(red);
//    m_drawer->position(Ogre::Vector3(.0f, .0f, .0f));
//    m_drawer->colour(red);
//    m_drawer->position(Ogre::Vector3(.5f * width, .0f, .0f));
//    m_drawer->colour(red);
//    m_drawer->triangle(0, 1, 2);
    m_drawer->end();
    m_scn->getRootSceneNode()->createChildSceneNode("DrawerNode")->attachObject(m_drawer);
    
//    Ogre::Entity *m_pCubeEntity = m_scn->createEntity("Cube", "ogrehead.mesh");
//    Ogre::SceneNode *m_pCubeNode = m_scn->getRootSceneNode()->createChildSceneNode("CubeNode");
//    m_pCubeNode->attachObject(m_pCubeEntity);
    
    m_physics_world = new b2World(b2Vec2(0, -9.8f));
    Ogre::ManualObject *prim = m_scn->createManualObject("PhysicsDrawer");
    m_scn->getRootSceneNode()->createChildSceneNode("PhysicsDrawerNode")->attachObject(prim);
    m_physics_drawer = new PhysicsDraw(prim);
    m_physics_world->SetDebugDraw(m_physics_drawer);
    
    // test physics drawer
    b2BodyDef body_def;
    b2CircleShape *circle_shape = new b2CircleShape;
    circle_shape->m_radius = 150.0f;
    circle_shape->m_p.Set(250.0f, 250.0f);
    b2Body *body = m_physics_world->CreateBody(&body_def);
    body->CreateFixture(circle_shape, 10);
    m_physics_drawer->SetFlags(b2Draw::e_shapeBit);
    
    g_active_canvas = this;
}
    
Canvas::~Canvas()
{
    if (NULL != m_physics_drawer)
    {
        delete m_physics_drawer;
    }
    if (NULL != m_drawer)
    {
        m_scn->destroyManualObject(m_drawer);
    }
    if (NULL != m_script_obj)
    {
        m_script_obj->c_obj = NULL;
        m_script_obj = NULL;
    }
    m_scn->destroyCamera(m_cam);
    Ogre::Root::getSingleton().destroySceneManager(m_scn);
    delete m_physics_world;
}
    
Ogre::Camera* Canvas::GetCamera() const
{
    return m_cam;
}
    
const char* Canvas::GetName() const
{
    return m_name.c_str();
}

void Canvas::SetName(const char *name)
{
    if (NULL == name)
    {
        return;
    }
    m_name = name;
}
    
    void Canvas::Update()
    {
        if (m_show_physics)
        {
            m_physics_world->DrawDebugData();
        }
        m_physics_drawer->Render();
    }
}